<template>
  <div class="employees-container">
    <div class="app-container">
      <!-- 通用工具栏组件使用 -->
      <page-tools>
        <!-- 自定义左侧内容 -->
        <template #slot-left>
          <span>共{{ total }}条记录</span>
        </template>

        <!-- 自定义右侧内容 -->
        <template #slot-right>
          <el-button type="danger" size="small" @click="uploadExcel">导入excel</el-button>
          <el-button type="success" size="small" @click="handleDownload">导出excel</el-button>
          <!-- <el-button type="success" size="small" @click="dataProcess">测试处理函数</el-button> -->
          <el-button type="primary" size="small" @click="addEmployees">新增员工</el-button>
        </template>
      </page-tools>

      <el-card style="margin-top: 10px;">
        <el-table :data="employeesList" border>
          <el-table-column type="index" label="序号" />
          <el-table-column prop="username" label="姓名" />
          <el-table-column prop="staffPhoto" label="头像">
            <template v-slot="scope">
              <el-avatar shape="square" :size="50" :src="scope.row.staffPhoto||'https://cube.elemecdn.com/9/c2/f0ee8a3c7c9638a54940382568c9dpng.png'" />
            </template>
          </el-table-column>
          <el-table-column prop="mobile" label="手机号" />
          <el-table-column prop="workNumber" label="工号" />
          <el-table-column label="聘用形式">
            <template v-slot="scope">
              <span>{{ scope.row.formOfEmployment*1===1?'正式':scope.row.formOfEmployment*1===2?'非正式':'未知' }}</span>
            </template>
          </el-table-column>
          <el-table-column prop="departmentName" label="部门" />
          <el-table-column prop="timeOfEntry" label="入职时间">
            <template slot-scope="scope">
              <span>{{ formatTime(scope.row.timeOfEntry) }}</span>
            </template>
          </el-table-column>
          <el-table-column label="账户状态" />
          <el-table-column label="操作" width="280">
            <template v-slot="scope">
              <el-button type="text" size="small" @click="detailFn(scope.row.id)">查看</el-button>
              <el-button type="text" size="small" @click="assignRoles(scope.row.id)">分配角色</el-button>
              <el-button type="text" size="small" @click="delEmphasis(scope.row.id)">删除</el-button>
            </template>
          </el-table-column>
        </el-table>

        <!-- 分页组件 -->
        <el-row type="flex" justify="center" align="middle" style="height: 60px">
          <!-- 分页区域 -->
          <el-pagination
            :current-page="query.page"
            :page-sizes="[10, 15, 20, 25]"
            :page-size="query.size"
            layout="total, sizes, prev, pager, next, jumper"
            :total="total"
            @size-change="handleSizeChange"
            @current-change="handleCurrentChange"
          />
        </el-row>
      </el-card>

      <!-- 新增员工--弹出框区域 -->
      <el-dialog
        title="提示"
        :visible.sync="dialogVisible"
        :before-close="handleClose"
      >
        <EmpDialog
          ref="dialogForm"
          :tree="Tree"
          :close.sync="dialogVisible"
          @formData="addEmployeesFn"
        />

      </el-dialog>

      <!-- 分配角色--弹出框区域 -->
      <el-dialog
        title="分配角色"
        :visible.sync="assignRolesDialogVisible"
      >
        <!--   @close="assignRolesDialogVisible"接收子组件发送来的close数据并赋值给 assignRolesDialogVisible-->
        <!-- :clicked-user-info="clickedUserInfo"向子组件发送名为 clickedUserInfo的数据包,包里的数据是 clickedUserInfo -->
        <!-- @checkList="assignRolesFn" 接收子组件发来的checkList数据包以形参传递给assignRolesFn函数-->
        <AssignRole
          :close.sync="assignRolesDialogVisible"
          :clicked-user-info="clickedUserInfo"
          :clicked-role-list="clickedRoleList"
          @checkList="assignRolesFn"
        />
      </el-dialog>
    </div>
  </div>
</template>

<script>

import { getEmployeesAPI, delEmployeesAPI, addEmployeesAPI, getUserDetailByIdAPI, assignRolesAPI } from '@/api/employees'
import { getDepartmentsAPI } from '@/api/department'
import { getRoleAPI } from '@/api/setting'
import AssignRole from './components/AssignRole.vue'
import dayjs from 'dayjs'

// 树形数据生成函数,用于将后端数据处理成树形
function transTree(list, rootValue) {
  const treeData = []

  // 2. 对传入的数据进行格式化
  list.forEach(item => {
    // 3. 判断每一项的 pid 是否等于传入的顶级 pid 一致
    if (item.pid === rootValue) {
      // 4. 如果有一致的数据，在将当前这一项的 id 作为顶级对象传入 transTree
      //    查看自己本身是否依然有子级分类，以此递归
      const children = transTree(list, item.id)

      // 5. 判断返回的 children 进行判断
      //    如果返回空数组，说明没有子级分类，不做任何处理
      if (children.length) {
        item.children = children
      }

      // 6. 最终直接将当前数据 push 到treeData即可
      treeData.push(item)
    }
  })

  return treeData
}

// 引入新增员工的表单组件
import EmpDialog from './EmpDialog.vue'
export default {
  name: 'Employees',
  components: {
    EmpDialog,
    AssignRole
  },
  data() {
    return {
      query: {
        page: 1, // 页码
        size: 10 // 每页条数
      },
      employeesList: [], // 员工列表

      total: 0, // 数据总条数
      // 添加角色控制对话框的显示
      dialogVisible: false,

      // 分配角色控制对话框的显示
      assignRolesDialogVisible: false,

      // 部门列表的树形结构
      Tree: {},

      // 被点击的员工的信息
      clickedUserInfo: {},

      // 所有角色的列表
      clickedRoleList: []

    }
  },
  created() {
    // 获取员工列表
    this.getEmployeesFn()
    // 获取部门列表,传给子组件-弹出框
    this.getDepartmentsFn()
    // 获取所有角色
    this.getRoleFn()
  },

  methods: {
    // 每页显示的条数发生改变时触发
    handleSizeChange(newSize) {
      // 将新页面的条数赋值
      this.query.size = newSize
      // 重新获取当前页员工列表
      this.getEmployeesFn()
    },

    // 当前页面发生改变时触发
    handleCurrentChange(newPage) {
      // console.log(newPage)
      // 将新页面的页脚赋值
      this.query.page = newPage
      // 重新获取当前页员工列表
      this.getEmployeesFn()
    },

    // 获取员工列表
    async getEmployeesFn() {
      const res = await getEmployeesAPI(this.query)
      // console.log(res)
      this.employeesList = res.data.rows
      this.total = res.data.total
    },

    // 获取部门列表
    async getDepartmentsFn() {
      const res = await getDepartmentsAPI()
      // console.log(res)
      this.Tree = transTree(res.data.depts, '')
      // console.log(this.Tree)
    },

    // 删除员工
    async delEmphasis(id) {
      // console.log(id)
      const res = await delEmployeesAPI(id)
      // console.log(res)
      if (this.employeesList.length === 1) {
        this.query.page--
        if (this.query.page < 1) {
          this.query.page = 1
        }
      }
      if (res.success) {
        // 成功提示
        this.$message.success(res.message)
        // 刷新页面
        this.getEmployeesFn()
      }
    },

    // 格式化时间
    formatTime(time) {
      return dayjs(time).format('YYYY-MM-DD')
    },

    // 新增员工
    addEmployees() {
      this.dialogVisible = true
      // console.log(111)
    },

    // 对话框关闭前的回调函数
    handleClose(done) {
      this.dialogVisible = false
      // 清空表单
      // console.log(this.$refs.dialogForm.$refs.addForm.resetFields())
      this.$refs.dialogForm.$refs.addForm.resetFields()

      done()
    },

    // 向服务器发送添加员工API
    async  addEmployeesFn(data) {
      // console.log('这里是父组件的发送')
      // console.log(data)
      const res = await addEmployeesAPI(data)
      // console.log(res)
      if (res.success) {
        this.$message.success(res.message)
        // 刷新页面
        this.getEmployeesFn()
      }
    },

    // 上传excel
    uploadExcel() {
      this.$router.push('/excel')
    },

    // 下载excel
    async handleDownload() {
      // 准备数据,从服务器中拿到所有的用户信息
      // **拿到数据
      const res = await getEmployeesAPI({
        page: 1, // 页码
        size: this.total // 每页条数,一次性拿到所有数据
      })
      // *************下载功能****************************************
      import('@/vendor/Export2Excel.js').then(excel => {
        // 文件表头
        const tHeader = ['序号', '姓名', '头像', '手机号', '工号', '聘用形式', '部门', '入职时间']

        // 文件内容,注意数据格式
        // **处理数据,调用数据处理函数将数据格式处理好
        const data = this.dataProcess(res.data.rows)
        // console.log(data)
        excel.export_json_to_excel({
          // 文件表头
          header: tHeader,
          // 文件内容
          data: data,
          // 文件名字
          filename: '员工名单',
          // 自动每个格子的宽度
          autoWidth: true,
          bookType: 'xlsx'
        })
        // this.downloadLoading = false
      })
    },

    // 数据处理函数
    dataProcess(List) {
      // 该函数的目的是将从服务器拿到的英文数组数据,按表头要求的顺序,将数组的值重新排列
      // -------------------------------------
      // 1.定义表头
      const tHeader = ['序号', '姓名', '头像', '手机号', '工号', '聘用形式', '部门', '入职时间']

      // 2.定义转换规则
      const myObj = {
        '姓名': 'username',
        '头像': 'staffPhoto',
        '手机号': 'mobile',
        '工号': 'workNumber',
        '聘用形式': 'formOfEmployment',
        '部门': 'departmentName',
        '入职时间': 'timeOfEntry',

        '编号': 'id',
        '密码': 'password',
        '转正日期': 'correctionTime '
      }

      // 遍历List数组,将英文key值拿出来,找到对应的中文,
      // 新建中文key,将英文key所对应的值放在中文key下
      // 举例:
      // List = [
      //   { correctionTime: '111111', departmentName: '总裁办' },
      //   { correctionTime: '222222', departmentName: '总裁办' }]
      const colArr = []
      // 3.开始遍历List数组,取出里边的对象的值并按表头顺序排列
      List.map((item, index) => {
        // 定义一个空数组,用于按顺序存放item对象的值
        const rowArr = []
        // console.log(item)
        // 通过遍历表头,拿到中文key,zhkey
        tHeader.map(zhKey => {
          // 通过中文key再myObj中找到对应的英文key
          // 用英文key就能在List里取到对应的值了
          // 找到对应的值之后将值按顺序放进新数组
          if (zhKey === '序号') {
            // 当取到序号的时候,指定值为 index+1
            rowArr.push(index + 1)
          } else {
            const enKey = myObj[zhKey]
            rowArr.push(item[enKey])
          }
        })
        // 将List数组中的一个对象遍历完成后
        // 就会产生一个rowArr数组,这个数组值的排列顺义与表头一致
        // 将rowArr数组,放进一个更大的数组中colArr数组
        colArr.push(rowArr)
        // rowArr就是我们想要的数组
      })
      // console.log(colArr)
      return colArr
      // dataProcess底部
    },

    // 员工详情
    detailFn(id) {
      this.$router.push(`/employees/detail?id=${id}`)
    },

    // 分配角色-弹框
    // 被点击员工的id
    async assignRoles(id) {
      // 展示多选框
      this.assignRolesDialogVisible = true
      // 用员工的id查找该员工的角色信息
      const res = await getUserDetailByIdAPI(id)
      // 被点击的用户信息传给子组件
      this.clickedUserInfo = res.data
      // console.log(this.clickedUserInfo)
    },

    // 获取角色列表
    async getRoleFn() {
      // 第一次发送获得total,用来获取所有角色
      const res = await getRoleAPI()
      // console.log(res.data.total)
      // 第二次发送带上total就能获取全部
      const res2 = await getRoleAPI({
        page: 1, // 页码
        size: res.data.total // 每页条数
      })
      // console.log(res2)
      // 角色列表给子组件
      this.clickedRoleList = res2.data.rows
      // console.log(this.clickedRoleList)
    },

    // 分配角色弹框的取消
    cancleDialogFn() {
      this.assignRolesDialogVisible = false
    },

    // 分配角色完成后发送API
    async assignRolesFn(data) {
      const res = await assignRolesAPI(data)
      // console.log(res)
      if (res.success) {
        this.$message.success(res.message)
      }
    }
  }
}
</script>

<style lang="scss" scoped></style>
